package com.laoxiang.modules.system.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.laoxiang.execption.LxAdminException;
import com.laoxiang.modules.system.entity.SysRole;
import com.laoxiang.modules.system.entity.SysRoleMenu;
import com.laoxiang.modules.system.entity.dto.PageDTO;
import com.laoxiang.modules.system.entity.dto.SysRoleDTO;
import com.laoxiang.modules.system.entity.vo.QueryRoleVO;
import com.laoxiang.modules.system.entity.vo.UpdateRoleVO;
import com.laoxiang.modules.system.mapper.SysRoleMapper;
import com.laoxiang.modules.system.service.SysRoleMenuService;
import com.laoxiang.modules.system.service.SysRoleService;
import com.laoxiang.modules.system.service.SysUserRoleService;
import com.laoxiang.utils.AppHttpCodeEnum;
import com.laoxiang.utils.BeanCopyUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;


import java.util.ArrayList;
import java.util.List;
import java.util.Objects;

/**
 * 角色信息表(SysRole)表服务实现类
 *
 * @author db
 * @since 2023-07-13 20:51:09
 */
@Service
public class SysRoleServiceImpl extends ServiceImpl<SysRoleMapper, SysRole> implements SysRoleService {

    @Autowired
    private SysRoleMapper sysRoleMapper;

    @Autowired
    private SysRoleMenuService sysRoleMenuService;

    @Autowired
    private SysUserRoleService sysUserRoleService;

    @Override
    public PageDTO getRoleList(Integer pageNum, Integer pageSize, QueryRoleVO queryRoleVO) {
        // 构建查询条件
        LambdaQueryWrapper<SysRole> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.like(StringUtils.hasText(queryRoleVO.getRoleName()),SysRole::getRoleName,queryRoleVO.getRoleName());
        queryWrapper.eq(Objects.nonNull(queryRoleVO.getStatus()),SysRole::getStatus,queryRoleVO.getStatus());
        queryWrapper.orderByAsc(SysRole::getCreateTime);
        if(null != queryRoleVO.getCreateTime() && null != queryRoleVO.getUpdateTime()){
            queryWrapper.ge(SysRole::getCreateTime,queryRoleVO.getCreateTime()).le(SysRole::getUpdateTime,queryRoleVO.getUpdateTime());
        }

        if(Objects.isNull(pageNum)){
            pageNum = 1;
        }
        if(Objects.isNull(pageSize)){
            pageSize = 10;
        }

        // 转为DTO
        Page<SysRole> sysRolePage = sysRoleMapper.selectPage(new Page<>(pageNum, pageSize), queryWrapper);
        List<SysRoleDTO> sysRoleDTOList = BeanCopyUtils.copyBeanList(sysRolePage.getRecords(), SysRoleDTO.class);

        // 封装pageDTO
        PageDTO pageDTO = new PageDTO();
        pageDTO.setPageIndex(pageNum);
        pageDTO.setPageSize(pageSize);
        pageDTO.setTotal(sysRolePage.getTotal());
        pageDTO.setRows(sysRoleDTOList);

        return pageDTO;
    }

    @Override
    public int saveRole(SysRole sysRole) {
        int insertNum = sysRoleMapper.insert(sysRole);

        // 插入此角色拥有的菜单
        if(sysRole.getMenuIds() != null && (sysRole.getMenuIds().length>0)){
            insertRoleMenu(sysRole);
        }

        return insertNum;
    }

    private void insertRoleMenu(SysRole sysRole) {
        List<SysRoleMenu> sysRoleMenuList = new ArrayList<>();
        for(Long menuId:sysRole.getMenuIds()){
            SysRoleMenu sysRoleMenu = new SysRoleMenu();
            sysRoleMenu.setRoleId(sysRole.getId());
            sysRoleMenu.setMenuId(menuId);
            sysRoleMenuList.add(sysRoleMenu);
        }
        if(sysRoleMenuList.size()>0){
            sysRoleMenuService.saveBatch(sysRoleMenuList);
        }
    }

    @Override
    public int updateRole(SysRole sysRole) {
        // 先更新角色信息
        int updateNum = sysRoleMapper.updateById(sysRole);
        // 再删除原有的角色关联的菜单信息
        sysRoleMenuService.deleteRoleMenuByRoleId(sysRole.getId());
        // 然后再插入新的角色关联的菜单信息
        insertRoleMenu(sysRole);
        return updateNum;
    }

    @Override
    public SysRole getSysRoleById(Long roleId) {

        SysRole sysRole = sysRoleMapper.selectById(roleId);
        return sysRole;
    }

    @Override
    public int deleteRoleById(Long roleId) {

        // 先判断此角色有没有用户使用，如果有，不允许删除
        int count = sysUserRoleService.countUserRoleByRoleId(roleId);
        if(count >0 ){
            throw new LxAdminException(AppHttpCodeEnum.ROLE_USERED);
        }
        // 删除此角色关联的菜单
        sysRoleMenuService.deleteRoleMenuByRoleId(roleId);

        // 再删除角色信息
        int deleteNum = sysRoleMapper.deleteById(roleId);
        return deleteNum;
    }

    @Override
    public void batchDeleteRole(List<Long> roleIds) {

        for(int i = 0; i < roleIds.size(); i++){
            // 先判断此角色有没有用户使用，如果有，不允许删除
            int count = sysUserRoleService.countUserRoleByRoleId(roleIds.get(i));
            if(count >0 ){
                throw new LxAdminException(AppHttpCodeEnum.ROLE_USERED);
            }
            // 删除此角色关联的菜单
            sysRoleMenuService.deleteRoleMenuByRoleId(roleIds.get(i));
            sysRoleMapper.deleteById(roleIds.get(i));
        }


//        for(Long id:roleIds){
//            // 先判断此角色有没有用户使用，如果有，不允许删除
//            int count = sysUserRoleService.countUserRoleByRoleId(id);
//            if(count >0 ){
//                throw new LxAdminException(AppHttpCodeEnum.ROLE_USERED);
//            }
//            // 删除此角色关联的菜单
//            sysRoleMenuService.deleteRoleMenuByRoleId(id);
//            sysRoleMapper.deleteById(id);
//        }

    }

    @Override
    public void updateRoleStatus(UpdateRoleVO updateRoleVO) {
        SysRole sysRole = sysRoleMapper.selectById(updateRoleVO.getId());
        sysRole.setStatus(updateRoleVO.getStatus());
        sysRoleMapper.updateById(sysRole);
    }

    @Override
    public List<SysRole> getRoleList() {

        // 角色状态为启用状态
        LambdaQueryWrapper<SysRole> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(SysRole::getStatus,1);
        List<SysRole> sysRoleList = sysRoleMapper.selectList(queryWrapper);

        return sysRoleList;
    }
}

